package com.zhanglijie.improve.aqs.mix.readwrite;

import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.locks.Lock;

/**
 * @author zhanglijie
 * @version 1.0
 * @since 1.1.0 2022/10/30 0030 0:07
 *
 * 演示结果：
 * 读读不互斥：
 * readThread8 ====》开始get key is 8
 * readThread2 ====》开始get key is 2
 * readThread4 ====》开始get key is 4
 * readThread7 ====》开始get key is 7
 * readThread6 ====》开始get key is 6
 * readThread5 ====》开始get key is 5
 * readThread6==== 已经 get完毕
 * readThread7==== 已经 get完毕
 * readThread4==== 已经 get完毕
 * readThread2==== 已经 get完毕
 * readThread8==== 已经 get完毕
 * readThread3 ====》开始get key is 3
 * readThread5==== 已经 get完毕
 * readThread3==== 已经 get完毕
 *
 * 写一定互斥：
 * writeThread0 ====》开始put key is 0 val is 0
 * writeThread0=== put完毕
 * writeThread1 ====》开始put key is 1 val is 1
 * writeThread1=== put完毕
 * writeThread2 ====》开始put key is 2 val is 2
 * writeThread2=== put完毕
 * writeThread3 ====》开始put key is 3 val is 3
 * writeThread3=== put完毕
 * writeThread4 ====》开始put key is 4 val is 4
 * writeThread4=== put完毕
 * writeThread5 ====》开始put key is 5 val is 5
 * writeThread5=== put完毕
 * writeThread6 ====》开始put key is 6 val is 6
 * writeThread6=== put完毕
 * writeThread7 ====》开始put key is 7 val is 7
 * writeThread7=== put完毕
 * writeThread8 ====》开始put key is 8 val is 8
 *
 *
 */
public class MyReadWriteLockTest {
    public static void main(String[] args) {

        Cache cache = new Cache();
        //读线程
        for (int i = 0; i < 10; i++) {
            int finalI = i;
            new Thread(()->{
               cache.get(finalI +"");
           },"readThread"+i).start();
        }

        //写线程
        for (int i = 0; i < 10; i++) {
            int finalI = i;
            new Thread(()->{
                cache.put(finalI +"",finalI);
            },"writeThread"+i).start();
        }
    }

    static class Cache{
        MyReentrantLockReadWrite myReentrantLockReadWrite = new MyReentrantLockReadWrite();
        Lock readLock = myReentrantLockReadWrite.readLock();
        Lock writeLock = myReentrantLockReadWrite.writeLock();
        private Map map = new HashMap<String,Integer>();
        public void put(String key,Integer value){
            writeLock.lock();
            try {
                 System.out.println(Thread.currentThread().getName() + " ====》开始put key is " + key + " val is " + value);
                map.put(key, value);
                 System.out.println(Thread.currentThread().getName() + "=== put完毕");
            }finally {
                writeLock.unlock();
            }
        }

        public void get(String key){
            readLock.lock();
            try{
                System.out.println(Thread.currentThread().getName()+" ====》开始get key is "+ key);
                Integer val = (Integer)map.get(key);
                Thread.sleep(200);
                System.out.println(Thread.currentThread().getName()+"==== 已经 get完毕");
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                readLock.unlock();
            }

        }
    }
}
